Pointers in CPP

A pointer is a variable that holds the address of another variable in memory. Pointers are essential for managing dynamic memory, manipulating arrays, effectively passing big structures to functions, and enabling intricate data structures such as linked lists, trees, and graphs.

Pointer Basics:

Rather than the value of a variable, a pointer contains the variable's address. A pointer is a container for an address that points to the location of the data in memory, if you think of variables in C++ as data containers.

Declaring a Pointer:

An asterisk (*) is placed before the pointer variable name when declaring a pointer, along with the data type to which the pointer points.

Syntax:

datatype *var_name;

Example: 

int* ptr;  // Pointer to an integer

  • int* indicates that ptr is a pointer to an int.
  • ptr can store the memory address of an integer variable.

How Pointers Work:

A pointer is not always instantly pointed to a specific address in memory when it is declared. It has to be assigned a variable's address using the address-of operator (&).

Example:

int num = 10;
int* ptr = #  // ptr now holds the address of num

  • num is an integer variable with a value of 10.
  • &num is the address of the variable num.
  • ptr is a pointer variable that holds the address of num

Dereferencing a Pointer:

The dereference operator (*) is used to retrieve the value that is kept at the memory address that a pointer is referring to.

Example:

int num = 10;
int* ptr = #

cout << "Value of num: " << num << endl;     // Output: 10
cout << "Value of ptr (address of num): " << ptr << endl;   // Output: Address of num
cout << "Value at the address ptr points to: " << *ptr << endl;   // Output: 10

  • *ptr dereferences the pointer, accessing the value stored at the address held by ptr.

Arithmetic Pointer:

With arrays in particular, pointers can be increased or decremented to point to nearby memory regions. arithmetic pointer in C++ is dependent on the size of the data type that is being referenced.

Example:


int arr[] = {10, 20, 30, 40};
int* ptr = arr;  // ptr points to the first element of arr

cout << *ptr << endl;   // Output: 10
ptr++;                  // Move to the next element
cout << *ptr << endl;   // Output: 20

  • When you increment the pointer (ptr++), it advances by the size of the type it points to (in this case, by sizeof(int)).

Pointers and Arrays:

In reality, an array name is only a constant pointer to the array's first entry. As a result, pointer arithmetic can be used to alter array elements.

int arr[] = {10, 20, 30};
int* ptr = arr;  // arr is a pointer to the first element of the array

cout << "First element: " << *ptr << endl;        // Output: 10
cout << "Second element: " << *(ptr + 1) << endl; // Output: 20

Null Pointer:

A pointer that points to no valid memory location is called a null pointer. Initializing pointers with NULL (earlier C++) or nullptr .

int* ptr = nullptr;  // or int* ptr = NULL; in older C++

Pointer to Pointer (Double Pointer):

A pointer that holds the address of another pointer is called a pointer to pointer. It comes in handy when you need to manage pointers at different levels or send pointers to functions.

int num = 10;
int* ptr = &num;      // Pointer to int
int** pptr = &ptr;    // Pointer to pointer to int

cout << **pptr << endl;  // Output: 10

  • pptr is a pointer that holds the address of ptr.
  • **pptr dereferences pptr twice to get the value of num.

Dynamic Memory Allocation:

  1. Allocating memory at run-time.
  2. Allocate and deallocate memory using “new” and “delete” operator
  3. new - allocates memory to a variable.
  4. delete - no longer needed
    1. It returns memory to the operating system
    2. This is known as deallocation.

int* ptr = new int;   // Allocate memory for an integer
*ptr = 10;            // Assign value to dynamically allocated memory

cout << *ptr << endl; // Output: 10

delete ptr;           // Free dynamically allocated memory

Example:

#include <iostream>
using namespace std;

int main() {

  // declare an int pointer
  int* pointInt;

  // declare a float pointer
  float* pointFloat;

  // dynamically allocate memory
  pointInt = new int;
  pointFloat = new float;

  // assigning value to the memory
  *pointInt = 45;
  *pointFloat = 45.45f;

  cout << *pointInt << endl;
  cout << *pointFloat << endl;

/*After assigning values to them and printing them,
we finally deallocate the memories using the code*/  
// deallocate the memory
  delete pointInt;
  delete pointFloat;

 
  return 0;
}

Pointers and Functions:

Large objects (such arrays or structures) can be effectively passed to functions by using pointers rather than copying the entire item.

Pass by Pointer Example:

void increment(int* ptr) {
    (*ptr)++;
}

int num = 10;
increment(&num);
cout << num << endl;  // Output: 11

  • the function increment() modifies the original variable because it is passed the memory address of num.

Pointers to Functions:

The address of a function is stored in a pointer to a function. Callback functions and polymorphism implementation benefit from this.

Example:

void display(int num) {
    cout << "Number: " << num << endl;
}

int main() {
    void (*funcPtr)(int) = &display;  // Pointer to function
    funcPtr(10);   // Calling function through pointer
}

Void Pointers:

A general pointer that can store the address of any kind of data is a void pointer. Before dereferencing it, the proper type must be cast.

Example:

void* ptr;
int num = 10;
ptr = &num;

cout << *(static_cast<int*>(ptr)) << endl;  // Output: 10



← Back Next →

Comments

Popular posts from this blog

Wrapper Class

Information Security & Essential Terminology

Information Security Threat Categories